from functools import wraps
from flask import jsonify
from flask_jwt_extended import jwt_required, get_jwt_identity
from app.models.user import User
from app.models import db
from sqlalchemy import text

def get_current_user():
    """获取当前登录用户"""
    current_user_id = get_jwt_identity()
    if current_user_id:
        # 处理字符串和整数类型的user_id
        try:
            user_id = int(current_user_id)
            return User.query.get(user_id)
        except (ValueError, TypeError):
            return None
    return None

def require_role(*allowed_roles):
    """基于角色的权限装饰器（已废弃，建议使用require_permission）"""
    def decorator(f):
        @wraps(f)
        @jwt_required()
        def decorated_function(*args, **kwargs):
            current_user = get_current_user()
            
            if not current_user:
                return jsonify({'error': '用户不存在'}), 404
            
            if not current_user.is_active:
                return jsonify({'error': '账户已被禁用'}), 403
            
            if current_user.role not in allowed_roles:
                return jsonify({'error': '权限不足'}), 403
            
            return f(*args, **kwargs)
        return decorated_function
    return decorator

def require_permission(*permission_codes):
    """基于权限代码的权限装饰器"""
    import logging
    logger = logging.getLogger(__name__)
    
    def decorator(f):
        @wraps(f)
        @jwt_required()
        def decorated_function(*args, **kwargs):
            current_user = get_current_user()
            
            logger.info(f"[DEBUG] require_permission called for function: {f.__name__}")
            logger.info(f"[DEBUG] Required permissions: {permission_codes}")
            logger.info(f"[DEBUG] Current user: {current_user.id if current_user else None}, role: {current_user.role if current_user else None}")
            
            if not current_user:
                logger.info(f"[DEBUG] User not found")
                return jsonify({'error': '用户不存在'}), 404
            
            if not current_user.is_active:
                logger.info(f"[DEBUG] User not active")
                return jsonify({'error': '账户已被禁用'}), 403
            
            # 检查用户是否拥有任一所需权限
            has_permission = False
            for code in permission_codes:
                logger.info(f"[DEBUG] Checking permission: {code}")
                # 检查角色权限和用户特殊权限
                check_query = text("""
                    SELECT COUNT(*) as count
                    FROM permissions p
                    LEFT JOIN role_permissions rp ON p.id = rp.permission_id AND rp.role = :role
                    LEFT JOIN user_permissions up ON p.id = up.permission_id AND up.user_id = :user_id
                    WHERE p.code = :code AND p.is_active = 1 
                      AND (rp.permission_id IS NOT NULL OR up.permission_id IS NOT NULL)
                """)
                
                try:
                    result = db.session.execute(check_query, {
                        'code': code,
                        'role': current_user.role,
                        'user_id': current_user.id
                    })
                    
                    count = result.scalar()
                    logger.info(f"[DEBUG] Permission check result for {code}: {count}")
                    
                    if count > 0:
                        has_permission = True
                        logger.info(f"[DEBUG] Permission {code} granted")
                        break
                except Exception as e:
                    logger.info(f"[DEBUG] Error checking permission {code}: {e}")
            
            logger.info(f"[DEBUG] Final permission result: {has_permission}")
            
            if not has_permission:
                logger.info(f"[DEBUG] Access denied - returning 403")
                return jsonify({'error': '权限不足'}), 403
            
            logger.info(f"[DEBUG] Access granted - proceeding to function")
            return f(*args, **kwargs)
        return decorated_function
    return decorator

def check_user_has_permission(user, permission_code):
    """检查用户是否拥有指定权限"""
    if not user or not user.is_active:
        return False
    
    check_query = text("""
        SELECT COUNT(*) as count
        FROM permissions p
        LEFT JOIN role_permissions rp ON p.id = rp.permission_id AND rp.role = :role
        LEFT JOIN user_permissions up ON p.id = up.permission_id AND up.user_id = :user_id
        WHERE p.code = :code AND p.is_active = 1 
          AND (rp.permission_id IS NOT NULL OR up.permission_id IS NOT NULL)
    """)
    
    result = db.session.execute(check_query, {
        'code': permission_code,
        'role': user.role,
        'user_id': user.id
    })
    
    return result.scalar() > 0
